package com.sunfeng.springcloud.controller;

import com.netflix.hystrix.contrib.javanica.annotation.DefaultProperties;
import com.netflix.hystrix.contrib.javanica.annotation.HystrixCommand;
import com.netflix.hystrix.contrib.javanica.annotation.HystrixProperty;
import com.sunfeng.springcloud.service.PaymentHystrixService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RestController;

import javax.annotation.Resource;

/**
 *
 * 在方法家异常处理   会造成代码臃肿
 * 可以配置 全局通用fallback
 * 这里有一个大坑
 * 关键在于feign:hystrix:enabled: true的作用，官网解释“Feign将使用断路器包装所有方法”，也就是将@FeignClient标记的那个service接口下所有的方法进行了hystrix包装
 *
 *
 * （类似于在这些方法上加了一个@HystrixCommand），
 * 这些方法会应用一个默认的超时时间为1s，所以你的service方法也有一个1s的超时时间，service1s就会报异常，controller立马进入备用方法，controller上那个3秒那超时时间就没有效果了。
 *
 * @author sunfeng
 * @date 2021/04/01 16:39
 **/
@Slf4j
@RestController
@DefaultProperties(defaultFallback = "payment_Global_FallbackMethod")//解决方法就  客户端端是使用统一的服务降级方法
public class OrderHystrixController {
    @Resource
    private PaymentHystrixService paymentHystrixService;

    @GetMapping("/consumer/payment/hystrix/ok/{id}")
    public String paymentInfo_OK(@PathVariable("id") Integer id)
    {
        String result = paymentHystrixService.paymentInfo_OK(id);
        return result;
    }

    /**
     *  服务降级
     *
     *  客户端服务超时  走服务降级   当调用的服务在规定时间内未返回想要的结果。 则走此处降级
     *
     * @param id
     * @return
     */
    @GetMapping("/consumer/payment/hystrix/timeout/{id}")
    @HystrixCommand(fallbackMethod = "paymentTimeOutFallbackMethod",commandProperties = {
            @HystrixProperty(name="execution.isolation.thread.timeoutInMilliseconds",value="3500")
    })
    // @HystrixCommand//用全局的fallback方法  这个需要加
    public String paymentInfo_TimeOut(@PathVariable("id") Integer id) {
       // int age = 10/0;

        // 这里调用超时会 走客户端全局的异常处理
        String result = paymentHystrixService.paymentInfo_TimeOut(id);

        return result;
    }



    @GetMapping("/consumer/payment/circuit/{id}")
    public String paymentInfo_Circuit(@PathVariable("id") Integer id)
    {
        String result = paymentHystrixService.paymentInfo_Circuit(id);
        return result;
    }


    /**
     * 善后方法
     * @param id
     * @return
     */
    public String paymentTimeOutFallbackMethod(@PathVariable("id") Integer id){
        return "我是消费者80,对方支付系统繁忙请10秒钟后再试或者自己运行出错请检查自己,o(╥﹏╥)o";
    }

    /**
     * 下面是全局fallback方法
     * @return
     */
    public String payment_Global_FallbackMethod()
    {
        return "Global异常处理信息，请稍后再试，/(ㄒoㄒ)/~~";
    }
}
